//
//  NSDictionary+MGSign.m
//  MoneyGoal_iOS
//
//  Created by yyb on 2022/8/23.
//  Copyright © 2022 Moneyease CO,. LTD. All rights reserved.
//

#import "NSDictionary+MGSign.h"

@implementation NSDictionary (MGSign)

static NSString * const aes128_seed = AES_KEY_DEV;

- (NSDictionary *)createSign {
    NSMutableDictionary *dict = [[NSMutableDictionary alloc] initWithDictionary:self];
    NSInteger cur_time = (int)[NSDate date].timeIntervalSince1970;
    [dict setObject:@(cur_time) forKey:@"cts"];
    
    // 先对所有的key排序
    // 从大到小
    NSArray *keys_sorted = [dict.allKeys sortedArrayUsingComparator:^NSComparisonResult(NSString * obj1, NSString * obj2) {
        return [obj2 compare:obj1];
    }];
    
    NSArray *keyValue_list = [keys_sorted map:^id(NSString *key, NSInteger index) {
        id value = [dict objectForKey:key];
        return [NSString stringWithFormat:@"%@=%@",key,value];
    }];
    
    // 组合成一个字符串
    NSString *sign_text = [self join:keyValue_list];
    
    sign_text = [sign_text stringByAppendingString:@"_MoneyGoal"];
    
    // base64
    NSData *sign_base64_data = [sign_text dataUsingEncoding:NSUTF8StringEncoding];
    NSString *sign_base64 = [sign_base64_data base64EncodedStringWithOptions:0];
    
    NSString *sign = [self AES128Encrypt:sign_base64 key:aes128_seed];
    [dict setObject:sign forKey:@"sign"];
    return dict;
}

- (NSString *)join:(NSArray *)list {
    NSString *text = @"";
    for (NSInteger index = 0; index < list.count; index ++) {
        NSString *content = list[index];
        if (index == 0) {
            text = content;
        } else {
            text = [NSString stringWithFormat:@"%@&%@",text,content];
        }
    }
    return text;
}

- (NSString *)AES128Encrypt:(NSString *)plainText key:(NSString *)key
{
      char keyPtr[kCCKeySizeAES128+1];
      memset(keyPtr, 0, sizeof(keyPtr));
      [key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];
        
      NSData* data = [plainText dataUsingEncoding:NSUTF8StringEncoding];
      NSUInteger dataLength = [data length];
        
      size_t bufferSize = dataLength + kCCBlockSizeAES128;
      void *buffer = malloc(bufferSize);
      size_t numBytesEncrypted = 0;
      CCCryptorStatus cryptStatus = CCCrypt(kCCEncrypt,
                                            kCCAlgorithmAES128,
                                            kCCOptionPKCS7Padding|kCCOptionECBMode,
                                            keyPtr,
                                            kCCBlockSizeAES128,
                                            NULL,
                                            [data bytes],
                                            dataLength,
                                            buffer,
                                            bufferSize,
                                            &numBytesEncrypted);
      if (cryptStatus == kCCSuccess) {
          NSData *resultData = [NSData dataWithBytesNoCopy:buffer length:numBytesEncrypted];
          return [resultData base64EncodedStringWithOptions:0];
      }
      free(buffer);
      return nil;
}

@end
